package com.ssy.lingxi.member.merchant.serviceimpl.feign;

import cn.hutool.core.collection.CollectionUtil;
import com.ssy.lingxi.common.constant.basic.EnableDisableStatus;
import com.ssy.lingxi.common.constant.member.MemberLevelTypeEnum;
import com.ssy.lingxi.common.constant.member.MemberStatusEnum;
import com.ssy.lingxi.common.constant.member.MemberTypeEnum;
import com.ssy.lingxi.common.constant.member.RoleTypeEnum;
import com.ssy.lingxi.common.exception.BusinessException;
import com.ssy.lingxi.common.response.ResponseCode;
import com.ssy.lingxi.common.response.Wrapper;
import com.ssy.lingxi.common.utils.DateTimeUtil;
import com.ssy.lingxi.common.utils.PasswordUtil;
import com.ssy.lingxi.member.merchant.api.constant.MemberRelationTypeEnum;
import com.ssy.lingxi.member.merchant.api.constant.MemberRightTypeEnum;
import com.ssy.lingxi.member.merchant.api.model.constant.MemberRightSpendTypeEnum;
import com.ssy.lingxi.member.merchant.api.model.vo.inner.request.*;
import com.ssy.lingxi.member.merchant.api.model.vo.inner.response.*;
import com.ssy.lingxi.member.merchant.entity.*;
import com.ssy.lingxi.member.merchant.model.constant.MemberValidateStatusEnum;
import com.ssy.lingxi.member.merchant.repository.MemberLevelConfigRepository;
import com.ssy.lingxi.member.merchant.repository.MemberRelationRepository;
import com.ssy.lingxi.member.merchant.repository.RoleRepository;
import com.ssy.lingxi.member.merchant.service.base.IBaseMemberCreditAsyncService;
import com.ssy.lingxi.member.merchant.service.base.IBaseMemberRightAsyncService;
import com.ssy.lingxi.member.merchant.service.feign.IMemberLevelRightCreditFeignService;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import javax.persistence.criteria.Predicate;
import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 会员等级（Level）、权益（Right）、信用（Credit）对外Feign服务接口实现类
 * @author 万宁
 * @version 2.0.0
 * @date 2020-10-20
 */
@Service
public class MemberLevelRightCreditFeignServiceImpl implements IMemberLevelRightCreditFeignService {
    @Resource
    private MemberRelationRepository relationRepository;

    @Resource
    private IBaseMemberRightAsyncService baseMemberRightAsyncService;

    @Resource
    private IBaseMemberCreditAsyncService baseMemberCreditAsyncService;

    @Resource
    private MemberLevelConfigRepository memberLevelConfigRepository;

    @Resource
    private RoleRepository roleRepository;


    /**
     * 查询平台会员的等级、权益、信用积分（多个）
     * @param memberIdList 接口参数
     * @return 平台会员的等级、权益、信用积分
     */
    @Override
    public Wrapper<List<MemberFeignLrcVO>> getPlatformMemberLrcBatch(List<Long> memberIdList) {
        List<MemberRelationDO> relationDOList = relationRepository.findAllBySubMemberIdInAndRelType(memberIdList, MemberRelationTypeEnum.PLATFORM.getCode());
        if(CollectionUtils.isEmpty(relationDOList)) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_RELATION_DOES_NOT_EXIST);
        }

        List<MemberFeignLrcVO> list = relationDOList.stream().map(a -> {
            MemberFeignLrcVO lrcVO = new MemberFeignLrcVO();
            lrcVO.setLevel(0);
            lrcVO.setLevelTag("");
            lrcVO.setScore(0);
            lrcVO.setSumReturnMoney(new BigDecimal(0));
            lrcVO.setSumPoint(0);
            lrcVO.setCurrentPoint(0);
            lrcVO.setSumUsedPoint(0);
            lrcVO.setCreditPoint(0);
            lrcVO.setTradeCommentPoint(0);
            lrcVO.setAfterSaleCommentPoint(0);
            lrcVO.setComplainPoint(0);
            lrcVO.setRegisterYearsPoint(0);
            lrcVO.setRegisterYears(DateTimeUtil.diffYears(a.getCreateTime(), LocalDateTime.now()));
            lrcVO.setMemberId(a.getSubMemberId());
            lrcVO.setRoleId(a.getSubRoleId());

            MemberLevelRightDO levelRightDO = a.getLevelRight();
            if (levelRightDO != null) {
                lrcVO.setLevel(levelRightDO.getLevel());
                lrcVO.setLevelTag(levelRightDO.getLevelTag());
                lrcVO.setScore(levelRightDO.getScore());
                lrcVO.setSumReturnMoney(levelRightDO.getSumReturnMoney());
                lrcVO.setSumPoint(levelRightDO.getSumPoint());
                lrcVO.setCurrentPoint(levelRightDO.getCurrentPoint());
                lrcVO.setSumUsedPoint(levelRightDO.getSumUsedPoint());
            }

            MemberCreditDO creditDO = a.getCredit();
            if (creditDO != null) {
                lrcVO.setCreditPoint(creditDO.getCreditPoint());
                lrcVO.setTradeCommentPoint(creditDO.getTradeCommentPoint());
                lrcVO.setAfterSaleCommentPoint(creditDO.getAfterSaleCommentPoint());
                lrcVO.setComplainPoint(creditDO.getComplainPoint());
                lrcVO.setRegisterYearsPoint(creditDO.getRegisterYearsPoint());
            }

            return lrcVO;
        }).collect(Collectors.toList());

        return Wrapper.success(list);
    }

    /**
     * 查询下级会员的价格权益
     * @param relationVO 接口参数
     * @return 下级会员在上级会员下的价格权益
     */
    @Override
    public Wrapper<MemberFeignRightVO> getMemberPriceRight(MemberFeignRelationVO relationVO) {
        return getSubMemberRight(MemberRightTypeEnum.PRICE_RIGHT, relationVO, BigDecimal.valueOf(1));
    }

    /**
     * 查询平台会员id
     * @return 查询结果
     */
    public MemberRelationDO getPlatformMemberRelationDO(){
        return relationRepository.findFirstByRelType(MemberRelationTypeEnum.PLATFORM.getCode());
    }

    public Wrapper<List<MemberFeignRightByOrderVO>> batchMemberPriceRightForOrder(MemberFeignBatchVO batchVO) {

        List<MemberFeignRightByOrderVO> collect=null;
        //查询平台会员id与角色id
        MemberRelationDO platformMemberRelation = getPlatformMemberRelationDO();
        MemberFeignUpperMemberVO ptMember = new MemberFeignUpperMemberVO();
        ptMember.setUpperMemberId(platformMemberRelation.getMemberId());
        ptMember.setUpperRoleId(platformMemberRelation.getRoleId());
        batchVO.getUpperMembers().add(ptMember);


        Specification<MemberRelationDO> specification = (root, query, criteriaBuilder) -> {
            List<Predicate> list = new ArrayList<>();
            list.add(criteriaBuilder.equal(root.get("subMemberId").as(Long.class), batchVO.getMemberId()));
            list.add(criteriaBuilder.equal(root.get("subRoleId").as(Long.class), batchVO.getRoleId()));

            List<Predicate> orList = new ArrayList<>();
            batchVO.getUpperMembers().forEach(upperMember -> orList.add(criteriaBuilder.and(criteriaBuilder.equal(root.get("memberId").as(Long.class), upperMember.getUpperMemberId()), criteriaBuilder.equal(root.get("roleId").as(Long.class), upperMember.getUpperRoleId()))));
            Predicate[] orPredicates = new Predicate[orList.size()];
            list.add(criteriaBuilder.or(orList.toArray(orPredicates)));

            Predicate[] p = new Predicate[list.size()];
            return criteriaBuilder.and(list.toArray(p));
        };
        List<MemberRelationDO> relations = relationRepository.findAll(specification);

        if(CollectionUtil.isNotEmpty(relations)){
            collect = relations.stream().map(o -> {
                MemberFeignRightByOrderVO resp = new MemberFeignRightByOrderVO();
                resp.setUpperMemberId(o.getMemberId());
                resp.setUpperRoleId(o.getRoleId());
                resp.setRelType(o.getRelType());
                resp.setCurrentPoint(o.getLevelRight().getCurrentPoint());
                resp.setUpperLogo(o.getMember().getLogo());
                resp.setUpperName(o.getMember().getName());
                return resp;
            }).collect(Collectors.toList());
        }
        return Wrapper.success(collect);
    }

    /**
     * 批量查询下级会员的价格权益
     *
     * @param batchVO 接口参数
     * @return 下级会员在上级会员下的价格权益
     */
    @Override
    public Wrapper<List<MemberFeignRightDetailVO>> batchMemberPriceRight(MemberFeignBatchVO batchVO) {
        Specification<MemberRelationDO> specification = (Specification<MemberRelationDO>) (root, query, criteriaBuilder) -> {
            List<Predicate> list = new ArrayList<>();
            list.add(criteriaBuilder.equal(root.get("subMemberId").as(Long.class), batchVO.getMemberId()));
            list.add(criteriaBuilder.equal(root.get("subRoleId").as(Long.class), batchVO.getRoleId()));

            List<Predicate> orList = new ArrayList<>();
            batchVO.getUpperMembers().forEach(upperMember -> orList.add(criteriaBuilder.and(criteriaBuilder.equal(root.get("memberId").as(Long.class), upperMember.getUpperMemberId()), criteriaBuilder.equal(root.get("roleId").as(Long.class), upperMember.getUpperRoleId()))));
            Predicate[] orPredicates = new Predicate[orList.size()];
            list.add(criteriaBuilder.or(orList.toArray(orPredicates)));

            Predicate[] p = new Predicate[list.size()];
            return criteriaBuilder.and(list.toArray(p));
        };

        List<MemberRelationDO> relations = relationRepository.findAll(specification);

        return Wrapper.success(batchVO.getUpperMembers().stream().map(upperMember -> {
            MemberFeignRightDetailVO detailVO = new MemberFeignRightDetailVO();
            detailVO.setUpperMemberId(upperMember.getUpperMemberId());
            detailVO.setUpperRoleId(upperMember.getUpperRoleId());
            detailVO.setRightTypeEnum(MemberRightTypeEnum.PRICE_RIGHT.getCode());
            detailVO.setParameter(BigDecimal.ONE);

            relations.stream().filter(r -> r.getMemberId().equals(upperMember.getUpperMemberId()) && r.getRoleId().equals(upperMember.getUpperRoleId()) && r.getVerified().equals(MemberValidateStatusEnum.VERIFY_PASSED.getCode()) && r.getStatus().equals(MemberStatusEnum.NORMAL.getCode())).findFirst().ifPresent(relation -> {
                detailVO.setSubMemberLevelType(relation.getSubMemberLevelTypeEnum());
                if(relation.getLevelRight() != null) {
                    if(relation.getLevelRight().getLevelConfig() != null) {
                        if(!CollectionUtils.isEmpty(relation.getLevelRight().getLevelConfig().getRights())) {
                            relation.getLevelRight().getLevelConfig().getRights().stream().filter(memberRightConfigDO -> memberRightConfigDO.getStatus().equals(EnableDisableStatus.ENABLE.getCode()) && memberRightConfigDO.getRightType().equals(MemberRightTypeEnum.PRICE_RIGHT.getCode())).findFirst().ifPresent(memberRightConfigDO -> detailVO.setParameter(memberRightConfigDO.getParameter()));
                        }
                    }
                }
            });
            return detailVO;
        }).collect(Collectors.toList()));
    }

    /**
     * 批量查询下级会员的价格权益
     *
     * @param feignRelations 接口参数
     * @return 下级会员在上级会员下的价格权益
     */
    @Override
    public Wrapper<List<MemberFeignRelationRightDetailVO>> batchMemberPriceRight(List<MemberFeignRelationVO> feignRelations) {
        Specification<MemberRelationDO> specification = (Specification<MemberRelationDO>) (root, query, criteriaBuilder) -> {
            List<Predicate> list = feignRelations.stream().map(batchVO ->
                criteriaBuilder.and(criteriaBuilder.equal(root.get("subMemberId").as(Long.class), batchVO.getSubMemberId()),
                criteriaBuilder.equal(root.get("subRoleId").as(Long.class), batchVO.getSubRoleId()),
                criteriaBuilder.equal(root.get("memberId").as(Long.class), batchVO.getUpperMemberId()),
                criteriaBuilder.equal(root.get("roleId").as(Long.class), batchVO.getUpperRoleId()))
            ).collect(Collectors.toList());

            Predicate[] p = new Predicate[list.size()];
            return criteriaBuilder.or(list.toArray(p));
        };

        List<MemberRelationDO> relationList = relationRepository.findAll(specification);
        return Wrapper.success(feignRelations.stream().map(feignRelation -> {
            MemberFeignRelationRightDetailVO detailVO = new MemberFeignRelationRightDetailVO();
            detailVO.setUpperMemberId(feignRelation.getUpperMemberId());
            detailVO.setUpperRoleId(feignRelation.getUpperRoleId());
            detailVO.setSubMemberId(feignRelation.getSubMemberId());
            detailVO.setSubRoleId(feignRelation.getSubRoleId());
            detailVO.setRightTypeEnum(MemberRightTypeEnum.PRICE_RIGHT.getCode());
            detailVO.setParameter(BigDecimal.ONE);
            MemberRelationDO relationDO = relationList.stream().filter(r -> r.getMemberId().equals(feignRelation.getUpperMemberId()) && r.getRoleId().equals(feignRelation.getUpperRoleId()) && r.getSubMemberId().equals(feignRelation.getSubMemberId()) && r.getSubRoleId().equals(feignRelation.getSubRoleId())).findFirst().orElse(null);
            if(relationDO != null && relationDO.getLevelRight() != null) {
                if(relationDO.getLevelRight().getLevelConfig() != null) {
                    if(!CollectionUtils.isEmpty(relationDO.getLevelRight().getLevelConfig().getRights())) {
                        relationDO.getLevelRight().getLevelConfig().getRights().stream().filter(memberRightConfigDO -> memberRightConfigDO.getStatus().equals(EnableDisableStatus.ENABLE.getCode()) && memberRightConfigDO.getRightType().equals(MemberRightTypeEnum.PRICE_RIGHT.getCode())).findFirst().ifPresent(memberRightConfigDO -> detailVO.setParameter(memberRightConfigDO.getParameter()));
                    }
                }
            }
            return detailVO;
        }).collect(Collectors.toList()));
    }

    /**
     * 查询下级会员的返现权益设置
     *
     * @param relationVO 接口参数
     * @return 下级会员在上级会员下的返现权益
     */
    @Override
    public Wrapper<MemberFeignRightVO> getMemberReturnRight(MemberFeignRelationVO relationVO) {
        return getSubMemberRight(MemberRightTypeEnum.RETURN_MONEY_RIGHT, relationVO, BigDecimal.ZERO);
    }

    /**
     * 查询下级会员在平台后台、上级会员下的返现权益设置
     *
     * @param relationVO 接口参数
     * @return 下级会员在上级会员下的返现权益
     */
    @Override
    public Wrapper<List<MemberFeignRightDetailVO>> findMemberReturnRight(MemberFeignRelationVO relationVO) {
        Specification<MemberRelationDO> specification = (Specification<MemberRelationDO>) (root, query, criteriaBuilder) -> {
            List<Predicate> list = new ArrayList<>();
            list.add(criteriaBuilder.equal(root.get("verified").as(Integer.class), MemberValidateStatusEnum.VERIFY_PASSED.getCode()));
            list.add(criteriaBuilder.equal(root.get("status").as(Integer.class), MemberStatusEnum.NORMAL.getCode()));
            list.add(criteriaBuilder.equal(root.get("subMemberId").as(Long.class), relationVO.getSubMemberId()));
            list.add(criteriaBuilder.equal(root.get("subRoleId").as(Long.class), relationVO.getSubRoleId()));

            List<Predicate> orList = new ArrayList<>();
            orList.add(criteriaBuilder.and(criteriaBuilder.equal(root.get("memberId").as(Long.class), relationVO.getUpperMemberId()), criteriaBuilder.equal(root.get("roleId").as(Long.class), relationVO.getUpperRoleId())));
            orList.add(criteriaBuilder.equal(root.get("relType").as(Integer.class), MemberRelationTypeEnum.PLATFORM.getCode()));
            Predicate[] orP = new Predicate[orList.size()];
            list.add(criteriaBuilder.or(orList.toArray(orP)));

            Predicate[] p = new Predicate[list.size()];
            return criteriaBuilder.and(list.toArray(p));
        };

        List<MemberRelationDO> relationList = relationRepository.findAll(specification);

        return Wrapper.success(relationList.stream().map(relationDO -> {
            MemberFeignRightDetailVO detailVO = new MemberFeignRightDetailVO();
            detailVO.setUpperMemberId(relationDO.getMemberId());
            detailVO.setUpperRoleId(relationDO.getRoleId());
            detailVO.setSubMemberLevelType(relationDO.getSubMemberLevelTypeEnum());
            detailVO.setRightTypeEnum(MemberRightTypeEnum.RETURN_MONEY_RIGHT.getCode());
            detailVO.setParameter(BigDecimal.ZERO);

            if(relationDO.getLevelRight() == null || relationDO.getLevelRight().getLevelConfig() == null || CollectionUtils.isEmpty(relationDO.getLevelRight().getLevelConfig().getRights())) {
                return detailVO;
            }

            MemberRightConfigDO rightConfigDO = relationDO.getLevelRight().getLevelConfig().getRights().stream().filter(right -> right.getRightType().equals(MemberRightTypeEnum.RETURN_MONEY_RIGHT.getCode())).findFirst().orElse(null);
            if(rightConfigDO == null || rightConfigDO.getParameter().compareTo(BigDecimal.ZERO) == 0) {
                return detailVO;
            }

            detailVO.setParameter(rightConfigDO.getParameter());
            return detailVO;
        }).collect(Collectors.toList()));
    }

    /**
     * 查询下级会员的等级、权益、信用积分
     * @param relationVO 接口参数
     * @return 下级会员在上级会员下的等级、权益、信用积分
     */
    @Override
    public Wrapper<MemberFeignLrcVO> getMemberLrc(MemberFeignRelationVO relationVO) {
        MemberRelationDO relationDO = relationRepository.findFirstByMemberIdAndRoleIdAndSubMemberIdAndSubRoleId(relationVO.getUpperMemberId(), relationVO.getUpperRoleId(), relationVO.getSubMemberId(), relationVO.getSubMemberId());
        if(relationDO == null || !relationDO.getStatus().equals(MemberStatusEnum.NORMAL.getCode()) || !relationDO.getVerified().equals(MemberValidateStatusEnum.VERIFY_PASSED.getCode())) {
            return Wrapper.success(null);
        }

        MemberFeignLrcVO lrcVO = new MemberFeignLrcVO();
        lrcVO.setLevel(0);
        lrcVO.setLevelTag("");
        lrcVO.setScore(0);
        lrcVO.setSumReturnMoney(new BigDecimal(0));
        lrcVO.setSumPoint(0);
        lrcVO.setCurrentPoint(0);
        lrcVO.setSumUsedPoint(0);
        lrcVO.setCreditPoint(0);
        lrcVO.setTradeCommentPoint(0);
        lrcVO.setAfterSaleCommentPoint(0);
        lrcVO.setComplainPoint(0);
        lrcVO.setRegisterYearsPoint(0);
        lrcVO.setRegisterYears(DateTimeUtil.diffYears(relationDO.getCreateTime(), LocalDateTime.now()));

        MemberLevelRightDO levelRightDO = relationDO.getLevelRight();
        if(levelRightDO != null) {
            lrcVO.setLevel(levelRightDO.getLevel());
            lrcVO.setLevelTag(levelRightDO.getLevelTag());
            lrcVO.setScore(levelRightDO.getScore());
            lrcVO.setSumReturnMoney(levelRightDO.getSumReturnMoney());
            lrcVO.setSumPoint(levelRightDO.getSumPoint());
            lrcVO.setCurrentPoint(levelRightDO.getCurrentPoint());
            lrcVO.setSumUsedPoint(levelRightDO.getSumUsedPoint());
        }

        MemberCreditDO creditDO = relationDO.getCredit();
        if(creditDO != null) {
            lrcVO.setCreditPoint(creditDO.getCreditPoint());
            lrcVO.setTradeCommentPoint(creditDO.getTradeCommentPoint());
            lrcVO.setAfterSaleCommentPoint(creditDO.getAfterSaleCommentPoint());
            lrcVO.setComplainPoint(creditDO.getComplainPoint());
            lrcVO.setRegisterYearsPoint(creditDO.getRegisterYearsPoint());
        }

        return Wrapper.success(lrcVO);
    }

    /**
     * 查询平台会员的等级、权益、信用积分
     * @param feignVO 接口参数
     * @return 平台会员的等级、权益、信用积分
     */
    @Override
    public Wrapper<MemberFeignLrcVO> getPlatformMemberLrc(MemberFeignVO feignVO) {
        MemberRelationDO relationDO = relationRepository.findFirstBySubMemberIdAndSubRoleIdAndRelType(feignVO.getMemberId(), feignVO.getRoleId(), MemberRelationTypeEnum.PLATFORM.getCode());
        if(relationDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_RELATION_DOES_NOT_EXIST);
        }

        MemberFeignLrcVO lrcVO = new MemberFeignLrcVO();
        lrcVO.setLevel(0);
        lrcVO.setLevelTag("");
        lrcVO.setScore(0);
        lrcVO.setSumReturnMoney(new BigDecimal(0));
        lrcVO.setSumPoint(0);
        lrcVO.setCurrentPoint(0);
        lrcVO.setSumUsedPoint(0);
        lrcVO.setCreditPoint(0);
        lrcVO.setTradeCommentPoint(0);
        lrcVO.setAfterSaleCommentPoint(0);
        lrcVO.setComplainPoint(0);
        lrcVO.setRegisterYearsPoint(0);
        lrcVO.setRegisterYears(DateTimeUtil.diffYears(relationDO.getCreateTime(), LocalDateTime.now()));

        MemberLevelRightDO levelRightDO = relationDO.getLevelRight();
        if(levelRightDO != null) {
            lrcVO.setLevel(levelRightDO.getLevel());
            lrcVO.setLevelTag(levelRightDO.getLevelTag());
            lrcVO.setScore(levelRightDO.getScore());
            lrcVO.setSumReturnMoney(levelRightDO.getSumReturnMoney());
            lrcVO.setSumPoint(levelRightDO.getSumPoint());
            lrcVO.setCurrentPoint(levelRightDO.getCurrentPoint());
            lrcVO.setSumUsedPoint(levelRightDO.getSumUsedPoint());
        }

        MemberCreditDO creditDO = relationDO.getCredit();
        if(creditDO != null) {
            lrcVO.setCreditPoint(creditDO.getCreditPoint());
            lrcVO.setTradeCommentPoint(creditDO.getTradeCommentPoint());
            lrcVO.setAfterSaleCommentPoint(creditDO.getAfterSaleCommentPoint());
            lrcVO.setComplainPoint(creditDO.getComplainPoint());
            lrcVO.setRegisterYearsPoint(creditDO.getRegisterYearsPoint());
        }

        return Wrapper.success(lrcVO);
    }

    /**
     * 获取下级会员的权益信息
     * @param rightTypeEnum 会员权益枚举，定义在MemberRightTypeEnum中
     * @param relationVO 来自OpenFeign对外接口的参数
     * @param defaultParameter 如果权益为null或参数为0（未设置），返回的默认参数值
     * @return 查询结果
     */
    private Wrapper<MemberFeignRightVO> getSubMemberRight(MemberRightTypeEnum rightTypeEnum,  MemberFeignRelationVO relationVO, BigDecimal defaultParameter) {
        MemberFeignRightVO rightVO = new MemberFeignRightVO();
        rightVO.setName(rightTypeEnum.getMessage());
        rightVO.setRightTypeEnum(rightTypeEnum.getCode());
        rightVO.setParameter(defaultParameter);
        rightVO.setStatus(EnableDisableStatus.DISABLE.getCode());

        MemberRelationDO relationDO = relationRepository.findFirstByMemberIdAndRoleIdAndSubMemberIdAndSubRoleId(relationVO.getUpperMemberId(), relationVO.getUpperRoleId(), relationVO.getSubMemberId(), relationVO.getSubRoleId());
        if(relationDO == null || !relationDO.getVerified().equals(MemberValidateStatusEnum.VERIFY_PASSED.getCode()) || !relationDO.getStatus().equals(MemberStatusEnum.NORMAL.getCode())) {
            return Wrapper.success(rightVO);
        }

        MemberLevelRightDO levelRight = relationDO.getLevelRight();
        if(levelRight == null) {
            return Wrapper.success(rightVO);
        }

        MemberLevelConfigDO levelConfig = levelRight.getLevelConfig();
        if(levelConfig == null) {
            return Wrapper.success(rightVO);
        }

        if(CollectionUtils.isEmpty(levelConfig.getRights())) {
            return Wrapper.success(rightVO);
        }

        MemberRightConfigDO rightConfigDO = levelConfig.getRights().stream().filter(right -> right.getRightType().equals(rightTypeEnum.getCode())).findFirst().orElse(null);
        if(rightConfigDO == null || rightConfigDO.getParameter().compareTo(BigDecimal.ZERO) == 0) {
            return Wrapper.success(rightVO);
        }

        rightVO.setStatus(rightConfigDO.getStatus());
        rightVO.setParameter(rightConfigDO.getParameter());

        return Wrapper.success(rightVO);
    }

    /**
     * 订单完成后，计算等级积分、积分权益
     * @param orderVO 接口参数
     * @return 计算结果
     */
    @Override
    public Wrapper<MemberFeignReturnRightVO> calculateMemberLrcByOrder(MemberFeignOrderVO orderVO) {
        BigDecimal plusPoint = new BigDecimal(0);
        MemberRelationDO relationDO = relationRepository.findFirstByMemberIdAndRoleIdAndSubMemberIdAndSubRoleId(orderVO.getUpperMemberId(), orderVO.getUpperRoleId(), orderVO.getSubMemberId(), orderVO.getSubRoleId());
        if(relationDO != null && relationDO.getLevelRight() != null && relationDO.getLevelRight().getLevelConfig() != null && !CollectionUtils.isEmpty(relationDO.getLevelRight().getLevelConfig().getRights())) {
            MemberRightConfigDO memberRightConfigDO = relationDO.getLevelRight().getLevelConfig().getRights().stream().filter(right -> MemberRightTypeEnum.RETURN_MONEY_RIGHT.getCode().equals(right.getRightType())).findFirst().orElse(null);
            if(memberRightConfigDO != null && memberRightConfigDO.getStatus().equals(EnableDisableStatus.ENABLE.getCode()) && memberRightConfigDO.getParameter().compareTo(new BigDecimal(0)) > 0) {
                plusPoint =  new BigDecimal(Math.round(memberRightConfigDO.getParameter().doubleValue() * orderVO.getAmount()));
            }
        }

        //由于如果升级后，关联的权益会发生变化，所以要先计算权益，再计算等级
        baseMemberRightAsyncService.calculateMemberTradeRightThenLevelScore(orderVO.getUpperMemberId(), orderVO.getUpperRoleId(), orderVO.getSubMemberId(), orderVO.getSubRoleId(), orderVO.getAmount(), orderVO.getOrderNo());

//        //异步计算等级积分
//        baseMemberLevelAsyncService.calculateSubMemberTradeScore(orderVO.getUpperMemberId(), orderVO.getUpperRoleId(), orderVO.getSubMemberId(), orderVO.getSubRoleId(), orderVO.getAmount(), orderVO.getOrderNo());
//
//        //异步计算交易权益积分
//        baseMemberRightAsyncService.calculateMemberTradeRight(orderVO.getUpperMemberId(), orderVO.getUpperRoleId(), orderVO.getSubMemberId(), orderVO.getSubRoleId(), orderVO.getAmount(), orderVO.getOrderNo());

        return Wrapper.success(new MemberFeignReturnRightVO(plusPoint.doubleValue()));
    }


    /**
     * 积分支付订单，校验可用信用积分、支付密码，再异步计算下级会员的权益积分
     * @param spendVO 接口参数
     * @return 操作结果
     */
    @Override
    public Wrapper<Void> calculateMemberUsedRightPoint(MemberFeignRightSpendVO spendVO) {
        MemberRelationDO relationDO;
        if(spendVO.getRelType().equals(MemberRelationTypeEnum.PLATFORM.getCode())) {
            relationDO = relationRepository.findFirstBySubMemberIdAndSubRoleIdAndRelType(spendVO.getSubMemberId(), spendVO.getSubRoleId(), MemberRelationTypeEnum.PLATFORM.getCode());
        } else {
            relationDO = relationRepository.findFirstByMemberIdAndRoleIdAndSubMemberIdAndSubRoleId(spendVO.getUpperMemberId(), spendVO.getUpperRoleId(), spendVO.getSubMemberId(), spendVO.getSubRoleId());
        }

        if(relationDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_RELATION_DOES_NOT_EXIST);
        }

        //校验支付密码
        MemberDO memberDO = relationDO.getSubMember();
        if(memberDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_DOES_NOT_EXIST);
        }

        if(!StringUtils.hasLength(memberDO.getPayPassword())) {
            return Wrapper.fail(ResponseCode.MC_MS_PAY_PASSWORD_NOT_SET);
        }

        if(!PasswordUtil.instance().checkPassword(memberDO.getPayPassword(), spendVO.getPayPassword())) {
            return Wrapper.fail(ResponseCode.MC_MS_PAY_PASSWORD_INCORRECT);
        }

        //检查可用信用积分
        MemberLevelRightDO levelRight = relationDO.getLevelRight();
        if(levelRight == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_LEVEL_DOES_NOT_EXIST);
        }

        if(levelRight.getCurrentPoint().compareTo(spendVO.getUsedPoint()) < 0) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_RIGHT_POINT_IS_NOT_ENOUGH);
        }

        baseMemberRightAsyncService.calculateMemberRightSpendScore(relationDO, spendVO.getUsedPoint(), spendVO.getSpentType(), spendVO.getOrderNo());

        return Wrapper.success();
    }

    /**
     * 售后评论成功后，计算会员信用积分
     * @param commentVO 接口参数
     * @return 操作结果
     */
    @Override
    public Wrapper<Void> calculateMemberAfterSaleCreditPoint(MemberFeignAfterSaleCommentVO commentVO) {
        //异步计算积分，历史记录
        baseMemberCreditAsyncService.calculateMemberAfterSaleCommentCredit(commentVO.getCommentMemberId(), commentVO.getCommentRoleId(), commentVO.getReceivedMemberId(), commentVO.getReceivedRoleId(), commentVO.getAfterSaleTime(),commentVO.getStar(),commentVO.getProduct(),commentVO.getComment(),commentVO.getOrderNo());
        return Wrapper.success();
    }

    /**
     * 根据memberLevelConfigId查询会员等级配置信息
     * @param memberLevelConfigId 接口参数
     * @return 返回结果
     */
    @Override
    public Wrapper<List<MemberFeignLevelConfigVO>> getMemberLevelConfigBatch(List<Long> memberLevelConfigId) {
        if (CollectionUtils.isEmpty(memberLevelConfigId)) {
            return Wrapper.success(Collections.emptyList());
        }

        List<MemberLevelConfigDO> memberLevelConfigDOList = memberLevelConfigRepository.findAllById(memberLevelConfigId);
        List<RoleDO> roles = roleRepository.findAllById(memberLevelConfigDOList.stream().map(MemberLevelConfigDO::getSubRoleId).collect(Collectors.toList()));

        List<MemberFeignLevelConfigVO> resultList = memberLevelConfigDOList.stream().map(levelConfig -> {
            MemberFeignLevelConfigVO levelConfigVO = new MemberFeignLevelConfigVO();
            levelConfigVO.setId(levelConfig.getId());
            levelConfigVO.setLevel(levelConfig.getLevel());
            levelConfigVO.setLevelTag(levelConfig.getLevelTag());
            levelConfigVO.setMemberLevelType(levelConfig.getLevelType());
            levelConfigVO.setMemberLevelTypeName(MemberLevelTypeEnum.getCodeMsg(levelConfig.getLevelType()));
            levelConfigVO.setRoleId(levelConfig.getSubRoleId());

            roles.stream().filter(role -> role.getId().equals(levelConfig.getSubRoleId())).findFirst().ifPresent(role -> {
                levelConfigVO.setRoleName(role.getRoleName());
                levelConfigVO.setRoleType(role.getRoleType().getTypeEnum());
                levelConfigVO.setRoleTypeName(RoleTypeEnum.getName(role.getRoleType().getTypeEnum()));
                levelConfigVO.setMemberType(role.getMemberType().getTypeEnum());
                levelConfigVO.setMemberTypeName(MemberTypeEnum.getCodeMessage(role.getMemberType().getTypeEnum()));

            });
            return levelConfigVO;
        }).collect(Collectors.toList());

        return Wrapper.success(resultList);
    }

    /**
     * 积分抵扣订单金额，校验可用信用积分、支付密码，扣除积分
     * @param deductionVO 接口参数
     * @return 操作结果
     */
    @Transactional(rollbackFor = BusinessException.class)
    @Override
    public Wrapper<Void> calculateMemberDeductionRightPoint(MemberFeignRightDeductionVO deductionVO) {
        List<MemberRelationDO> relationDO=new ArrayList<>();
        Map<String, MemberFeignRightDeductionItemVO> reqMap = deductionVO.getItemList().stream().collect(Collectors.toMap(k -> k.getUpperMemberId() + ":" + k.getUpperRoleId(), v -> v, (v1, v2) -> v2));
        if(deductionVO.getRelType().equals(MemberRelationTypeEnum.PLATFORM.getCode())) {
            relationDO.add(relationRepository.findFirstBySubMemberIdAndSubRoleIdAndRelType(deductionVO.getSubMemberId(), deductionVO.getSubRoleId(), MemberRelationTypeEnum.PLATFORM.getCode()));
        } else {
            List<MemberRelationDO> bySubMemberIdAndRelType = relationRepository.findBySubMemberIdAndSubRoleIdAndRelType(deductionVO.getSubMemberId(),deductionVO.getSubRoleId(), MemberRelationTypeEnum.OTHER.getCode());
            if(CollectionUtil.isEmpty(bySubMemberIdAndRelType)) {
                return Wrapper.fail(ResponseCode.MC_MS_MEMBER_RELATION_DOES_NOT_EXIST);
            }
            relationDO=bySubMemberIdAndRelType.stream().filter(k ->reqMap.get(k.getMemberId() + ":" + k.getRoleId())!=null).collect(Collectors.toList());
        }

        if(CollectionUtil.isEmpty(relationDO)) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_RELATION_DOES_NOT_EXIST);
        }

        //校验支付密码
        MemberDO memberDO = relationDO.get(0).getSubMember();
        if(memberDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_DOES_NOT_EXIST);
        }

        //检查可用信用积分
        for(MemberRelationDO relation:relationDO){
            MemberLevelRightDO levelRight = relation.getLevelRight();
            if(levelRight == null) {
                return Wrapper.fail(ResponseCode.MC_MS_MEMBER_LEVEL_DOES_NOT_EXIST);
            }

            MemberFeignRightDeductionItemVO deductionItemVO = reqMap.get(relation.getMemberId() + ":" + relation.getRoleId());
            if(deductionItemVO == null) {
                return Wrapper.fail(ResponseCode.MC_MS_MEMBER_LEVEL_DOES_NOT_EXIST);
            }

            if(levelRight.getCurrentPoint().compareTo(deductionItemVO.getUsedPoint()) < 0) {
                return Wrapper.fail(ResponseCode.MC_MS_MEMBER_RIGHT_POINT_IS_NOT_ENOUGH);
            }

            baseMemberRightAsyncService.calculateMemberRightSpendScore(relation, deductionItemVO.getUsedPoint(), MemberRightSpendTypeEnum.DEDUCTION_AMOUNT.getTypeEnum(), deductionItemVO.getOrderNo());
        }
        return Wrapper.success();
    }


    /**
     * 返还-抵扣订单金额的积分
     * @param returnVO 接口参数
     * @return 操作结果
     */
    @Transactional(rollbackFor = BusinessException.class)
    @Override
    public Wrapper<Void> returnMemberRightPoint(MemberFeignRightReturnVO returnVO) {
        return baseMemberRightAsyncService.returnMemberRightPoints(returnVO.getSubMemberId(),returnVO.getSubRoleId(),MemberRightSpendTypeEnum.DEDUCTION_AMOUNT.getTypeEnum(),returnVO.getOrderNo(),"取消订单"+returnVO.getOrderNo());
    }

    /**
     * 根据上级会员Id和上级会员角色Id，以及当前用户，查询价格权益参数设置
     *
     * @param upperVO 接口参数
     * @return 查询结果
     */
    @Override
    public Wrapper<MemberFeignManageMemberCreditParameterVO> getUpperMemberCreditParameter(MemberFeignManageUpperMemberAndRoleVO upperVO) {
        MemberFeignManageMemberCreditParameterVO parameterVO = new MemberFeignManageMemberCreditParameterVO();
        parameterVO.setParameter(new BigDecimal(1));
        //查询上下级关系
        MemberRelationDO relationDO = relationRepository.findFirstByMemberIdAndRoleIdAndSubMemberIdAndSubRoleId(upperVO.getParentMemberId(), upperVO.getParentMemberRoleId(), upperVO.getSubMemberId(), upperVO.getSubMemberRoleId());
        if (relationDO == null || !relationDO.getVerified().equals(MemberValidateStatusEnum.VERIFY_PASSED.getCode()) || !relationDO.getStatus().equals(MemberStatusEnum.NORMAL.getCode())) {
            return Wrapper.success(parameterVO);
        }

        MemberLevelRightDO levelRight = relationDO.getLevelRight();
        if (levelRight == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_LEVEL_DOES_NOT_EXIST);
        }

        MemberLevelConfigDO levelConfig = levelRight.getLevelConfig();
        if (levelConfig == null) {
            return Wrapper.success(parameterVO);
        }

        if (CollectionUtils.isEmpty(levelConfig.getRights())) {
            return Wrapper.success(parameterVO);
        }

        MemberRightConfigDO configDO = levelConfig.getRights().stream().filter(config -> MemberRightTypeEnum.PRICE_RIGHT.getCode().equals(config.getRightType())).findFirst().orElse(null);
        if (configDO == null || configDO.getStatus().equals(EnableDisableStatus.DISABLE.getCode()) || configDO.getParameter().compareTo(BigDecimal.ZERO) == 0) {
            return Wrapper.success(parameterVO);
        }

        parameterVO.setParameter(configDO.getParameter());

        return Wrapper.success(parameterVO);
    }

    /**
     * 查询下级会员在上级会员下的等级
     *
     * @param feignVO 接口参数
     * @return 查询结果
     */
    @Transactional
    @Override
    public Wrapper<List<MemberFeignLevelDetailVO>> findSubMemberLevels(MemberFeignVO feignVO) {
        Specification<MemberRelationDO> specification = (Specification<MemberRelationDO>) (root, query, criteriaBuilder) -> {
            List<Predicate> list = new ArrayList<>();
            list.add(criteriaBuilder.equal(root.get("subMemberId").as(Long.class), feignVO.getMemberId()));
            list.add(criteriaBuilder.equal(root.get("subRoleId").as(Long.class), feignVO.getRoleId()));
            list.add(criteriaBuilder.equal(root.get("status").as(Integer.class), MemberStatusEnum.NORMAL.getCode()));
            list.add(criteriaBuilder.equal(root.get("verified").as(Integer.class), MemberValidateStatusEnum.VERIFY_PASSED.getCode()));

            Predicate[] p = new Predicate[list.size()];
            return criteriaBuilder.and(list.toArray(p));
        };
        List<MemberRelationDO> result = relationRepository.findAll(specification);
        return Wrapper.success(result.stream().map(relationDO -> {
            MemberFeignLevelDetailVO detailVO = new MemberFeignLevelDetailVO();
            detailVO.setUpperMemberId(relationDO.getMemberId());
            detailVO.setUpperRoleId(relationDO.getRoleId());
            detailVO.setRelType(relationDO.getRelType());
            detailVO.setLevel(relationDO.getLevelRight() == null ? 0 : relationDO.getLevelRight().getLevel());
            detailVO.setLevelTag(relationDO.getLevelRight() == null ? "" : relationDO.getLevelRight().getLevelTag());
            return detailVO;
        }).collect(Collectors.toList()));
    }
}
